package com.example.baselibrary.utlis

import android.util.Log
import com.example.baselibrary.bases.Constants.DEBUG
import com.example.baselibrary.bases.Constants.TAG
import com.example.baselibrary.enums.MessageType
import com.example.baselibrary.eventbus.EventStringBus
import com.xuexiang.xui.utils.XToastUtils
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
import org.greenrobot.eventbus.EventBus

/**
 * 日志工具类
 * 提供调试日志、持久化日志和特殊事件处理功能
 *
 * @property DEBUG 是否调试模式
 * @property TAG 默认日志标签
 */
object LogUtils {
    private const val LOG_BORDER = "═════════════════════════════════"
    private const val LOG_ICON = "💡"
    private const val LOG_PREFIX = "║"
    private const val LOG_START = "╔"
    private const val LOG_END = "╚"

    // 标记SaveToFile是否可用
    private var isSaveToFileAvailable: Boolean = true

    /**
     * 信息日志（始终打印）
     * @param message 日志信息
     */
    fun info(message: String) {
        val formatted = buildString {
            appendLine("$LOG_START$LOG_BORDER")
            appendLine("$LOG_PREFIX $LOG_ICON $message")
            append("$LOG_END$LOG_BORDER")
        }
        Log.i(TAG, formatted)
    }

    /**
     * 保存日志到文件（带Toast提示）
     * @param message 日志信息
     * @param showToast 是否显示Toast提示
     * @param triggerVoice 是否触发语音事件
     */
    fun logEvent(
        message: String,
        showToast: Boolean = false,
        triggerVoice: Boolean = false
    ) {
        if (DEBUG) {
            info(message)
        }

        handleOptionalFeatures(message, showToast, triggerVoice)
        saveToFile(message)
    }

    /**
     * 保存HTTP相关日志
     * @param message 日志信息
     */
    fun saveHttpLog(message: String) {
        info(message)
        saveToFile(message)
    }

    /**
     * 处理可选功能（Toast和语音事件）
     */
    private fun handleOptionalFeatures(
        message: String,
        showToast: Boolean,
        triggerVoice: Boolean
    ) {
        if (showToast) {
            XToastUtils.info(message)
        }

        if (triggerVoice) {
             EventBus.getDefault().post(EventStringBus(message,null, MessageType.Voice))
        }
    }

    /**
     * 异步保存日志到文件
     */
    private fun saveToFile(message: String) {
        // 如果SaveToFile已知不可用，则直接返回
        if (!isSaveToFileAvailable) {
            return
        }

        CoroutineScope(Dispatchers.IO).launch {
            try {
                // 使用更安全的类加载方式
                val saveToFileClass = try {
                    Class.forName("com.example.baselibrary.utlis.SaveToFile", false, this::class.java.classLoader)
                } catch (e: Throwable) {
                    Log.w(TAG, "SaveToFile class cannot be loaded: ${e.message}")
                    isSaveToFileAvailable = false
                    return@launch
                }

                val method = try {
                    saveToFileClass.getMethod("writeLogToSDCard", String::class.java, String::class.java)
                } catch (e: Throwable) {
                    Log.w(TAG, "SaveToFile.writeLogToSDCard method not found: ${e.message}")
                    isSaveToFileAvailable = false
                    return@launch
                }

                method.invoke(null, "log", message)
            } catch (e: Throwable) {
                // 使用Throwable捕获所有异常，包括NoClassDefFoundError等Error
                Log.w(TAG, "Failed to save log to file: ${e.message}")
                isSaveToFileAvailable = false
            }
        }
    }
}
